package panda.server.util.datamine;

import java.io.File;
import java.util.Scanner;

import panda.client.enumerations.MagicSet;

/**
 * Mines the following data from Wizards of the Coast's Gatherer utility:<br>
 * .name<br>
 * .casting cost<br>
 * .type<br>
 * .pwr/tgh<br>
 * .rules text<br>
 * .rarity<br>
 * <br>
 * This class mines Gatherer's "text spoiler" for card information. Intended for use before magiccards.info uploads full
 * HQ scans and full card information.
 * 
 * @author zane.tian@gmail.com
 */
public class GathererOracleMiner {
	// private static final String setName = "Shards of Alara";

	public static void main(String[] args) {
		createMagicCardsFromSpoiler(MagicSet.CONFLUX);
	}

	/**
	 * Reads Gatherer "text spoiler" to create java code that initializes MagicCard objects.<br>
	 * In order to get the text file from Gatherer, paste the text spoiler into a text editor and replace all TABs with
	 * spaces. Card data should now be split by 3 spaces on a new line.
	 */
	private static void createMagicCardsFromSpoiler(MagicSet set) {
		try {
			/* TODO: why not UTF8? */
			Scanner scanner = new Scanner(new File("src/panda/cardutil/data/conflux-text-spoiler.txt"), "ISO-8859-1");

			String cardName;
			String castingCost;
			String type;
			String pwrtgh;
			String rulesText;
			String rarity;
			String cardDelimiter;
			int fauxID = 0;

			StringBuffer code = new StringBuffer();
			// HashMap<String, Integer> nameIdMap = getCorrectNameIdMap();
			
			String[] sortedByID = new String[set.getTotalCards()];

			/**
			 * Look for card information defined in the following format:<br>
			 * <br>
			 * CardName: Shorecrasher Mimic<br>
			 * Cost: 1(G/U)<br>
			 * Type: Creature - Shapeshifter<br>
			 * Pow/Tgh: 2/1<br>
			 * Rules Text: Whenever you play a spell that's both green and blue, Shorecrasher Mimic becomes 5/3 and gains
			 * trample until end of turn.<br>
			 * Set/Rarity: Eventide Common<br>
			 */
			while(scanner.hasNext()) {
				fauxID++;

				/* CardName: Shorecrasher Mimic */
				String nameLine[] = scanner.nextLine().split(": ");
				assert nameLine[0].equals("CardName");
				cardName = nameLine[1];

				/* Cost: 1(G/U) */
				String costLine[] = scanner.nextLine().split(": ");
				assert costLine[0].equals("Cost");
				castingCost = costLine.length == 2 ? costLine[1] : "";

				/* Type: Creature - Shapeshifter */
				String typeLine[] = scanner.nextLine().split(": ");
				assert typeLine[0].equals("Type");
				type = typeLine[1];

				/* Pow/Tgh: 2/1 */
				String powerLine[] = scanner.nextLine().split(": ");
				assert powerLine[0].equals("Pow/Tgh");
				pwrtgh = powerLine[1];

				/* Rules Text: Whenever you play a spell that's both green and blue... */

				/** logic is a bit different here because we need to account for ": " occuring in the rules text */
				String rulesLine = scanner.nextLine();
				int rulesDelimPos = rulesLine.indexOf(": ");
				assert rulesLine.substring(0, rulesDelimPos).equals("Rules Text");

				rulesText = rulesLine.substring(rulesDelimPos + 2);

				/* Set/Rarity: Eventide Common */
				String rarityLine = scanner.nextLine();
				int rarityDelimPos = rarityLine.indexOf(": ");
				assert rarityLine.substring(0, rarityDelimPos).equals("Set/Rarity");

				String rareTokens = rarityLine.substring(rarityDelimPos + 2);

				if(rareTokens.contains("BasicLand")) { /* BasicLand must be before Common because some basics are common */
					rarity = "Basic Land";
				} else if(rareTokens.contains("MythicRare")) {
					rarity = "Mythic Rare";
				} else if(rareTokens.contains("Rare")) {
					rarity = "Rare";
				} else if(rareTokens.contains("Uncommon")) {
					rarity = "Uncommon";
				} else if(rareTokens.contains("Common")) {
					rarity = "Common";
				} else {
					rarity = "error :P";
					assert false : "Card: " + cardName + " is not one of the defined rarity types";
				}

				/**
				 * output java code to instantiate a MagicCard: public MagicCard(MagicSet set, String name, String
				 * castingCost, String type, String bodyText, CardRarity rarity, String illustrator, int id)
				 */
				code.delete(0, code.length());

				code.append("cards.add(new MagicCard(set, \"");
				code.append(cardName);
				code.append("\", \"");
				code.append(castingCost);
				code.append("\", \"");

				if(pwrtgh.equals("/")) {
					code.append(type);
				} else {
					code.append(type + " " + pwrtgh);
				}

				code.append("\", \"");
				code.append(rulesText.replace("\"", "\\\"")); /* Some cards have quotes in their rules text. Must sanitize */
				code.append("\", ");

				if(rarity.equals("Mythic Rare")) {
					code.append("CardRarity.MYTHIC");
				} else if(rarity.equals("Rare")) {
					code.append("CardRarity.RARE");
				} else if(rarity.equals("Uncommon")) {
					code.append("CardRarity.UNCOMMON");
				} else if(rarity.equals("Common")) {
					code.append("CardRarity.COMMON");
				} else if(rarity.equals("Basic Land")) {
					code.append("CardRarity.LAND");
				} else {
					throw new IllegalStateException("CardRarity was not properly defined: " + rarity);
				}

				code.append(", \"");
				code.append("Prerelease Card");
				code.append("\", ");

				/**
				 * grab the correct ID from nameIdMap if it exists: manual editing is needed because BasicLands have
				 * multiple IDs
				 */
				code.append(fauxID);
				// code.append(nameIdMap.get(cardName));

				code.append("));");

				sortedByID[fauxID - 1] = code.toString();
				// sortedByID[nameIdMap.get(cardName) - 1] = code.toString();
				// System.out.println(code);
				// System.out.println("cardNames.add(\"" + cardName + "\");");

				/** Each card information block is separated by a blank line with 3 spaces */
				/** Check for end of file: text spoilers end when there is no 3 space separator line */
				if(scanner.hasNext()) {
					cardDelimiter = scanner.nextLine();
					assert cardDelimiter.equals("   ");
				} else {
					break;
				}
			}
			
			/** after we are done reading the file */
			for(String codeLine : sortedByID) {
				System.out.println(codeLine);
			}
			
		} catch(Exception ex) {
			ex.printStackTrace();
		}
	}
}